package com.dlc.felear.xiaoensale.helper;

import android.util.Log;

import com.dlc.felear.xiaoensale.utils.HexUtil;

import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.ScheduledThreadPoolExecutor;

public class IoInputHelper {
    private static final String TAG = "IoInputHelper";
    private Map<Byte, Byte> inputMaps;
    private Map<Byte, Byte> inputMapsLast;
    private ScheduledExecutorService scheduledThreadPool;
    private IoInputCallback ioInputCallback;
    private boolean isWork=true;

    public IoInputHelper(IoInputCallback ioInputCallback) {
        this.ioInputCallback = ioInputCallback;
        inputMaps = new HashMap<>();
        inputMapsLast = new HashMap<>();
        scheduledThreadPool = new ScheduledThreadPoolExecutor(2);
    }

    public void setEnable(){
        isWork=true;
    }

    public Map<Byte, Byte> getInputMaps() {
        return inputMaps;
    }


    public void inputStatus(final byte[] cmd) {
//        Log.e(TAG, "input="+ HexUtil.bytes2HexString(cmd));
        scheduledThreadPool.execute(new Runnable() {
            @Override
            public void run() {
                try {
                    for (int i = 3; i < cmd.length - 2; i ++) {
                        for (int j = 0; j < 8; j++) {
                            byte tt = getBit(cmd[i], j);
                            int key = 8 * (i-3) + j;
                            inputMaps.put((byte) key, tt);
                        }
                    }
                    listence();
//                    Log.e(TAG, "inputMapsLast=" + JsonHelper.toJson(inputMapsLast));
                } catch (Exception e) {
//                    Log.e(TAG, "inputStatus=" + e.getMessage());
                }
            }
        });
    }

    public byte getIoStatus(byte index) {
        return getMapValue(inputMaps, index);
    }

    public byte outNumToInNum(byte outNum) {
        byte temp = 0;
        switch (outNum) {
            case 6:
                temp = 10;
                break;
            case 8:
                temp = 12;
                break;
            case 10:
                temp = 14;
                break;
            case 12:
                temp = 16;
                break;
        }
        return temp;
    }

    /**
     * 监听输入IO状态
     */
    private void listence() {
        scheduledThreadPool.execute(new Runnable() {
            @Override
            public void run() {
                try {
                    for (byte b : inputMaps.keySet()) {
                        byte c_value = getMapValue(inputMaps, b);
                        byte l_value = getMapValue(inputMapsLast, b);
//                        if(b==11){
//                           Log.e(TAG,"c_value="+c_value+" l_value="+l_value);
//                        }
                        if (c_value != l_value && c_value == 1) {
                            ioTrigger(b);
                        }
                    }
//                    Log.e(TAG,"inputMaps="+JsonHelper.toJson(inputMaps));
                    inputMapsLast.clear();
                    inputMapsLast.putAll(inputMaps);
                } catch (Exception e) {
                    Log.e(TAG, e.getMessage());
                }
            }
        });
    }

    /**
     * 获取map的值
     *
     * @param map
     * @param key
     * @return
     */
    private byte getMapValue(Map<Byte, Byte> map, byte key) {
        if (!map.containsKey(key)) {
            return 0;
        }
        return map.get(key);
    }

    private byte getBit(byte b, int index) {
        return (byte) ((b >> index) & 0x01);
    }

    private void ioTrigger(int index) {
        Log.e(TAG, "触发开关:" + index);
        if (ioInputCallback != null&&isWork) {
            ioInputCallback.ioInputResult((byte) index);
        }
    }


    public void testInput(byte index) {
        byte temp = getMapValue(inputMaps, index);
        temp = (byte) (temp == 0 ? 1 : 0);
        inputMaps.put(index, temp);
        listence();
    }

    public interface IoInputCallback {
        void ioInputResult(byte index);
    }


}
